#ifndef __XML_UTILS_H__
#define __XML_UTILS_H__

#include <GSLAM/core/Svar.h>
#include <GSLAM/core/XML.h>

namespace tinyxml2 {


inline bool saveSvarXML(GSLAM::Svar& var, const char* filename)
{
    var.update();
    GSLAM::Svar::SvarMap data=var.get_data();

    XMLDocument doc;
    XMLElement* element = doc.NewElement("project");
    doc.InsertFirstChild(element);
    XMLDeclaration* declaration=doc.NewDeclaration();//添加xml文件头申明
    doc.InsertFirstChild(declaration);

    for(std::pair<std::string,std::string> it:data)
    {
        std::string name=it.first;
        XMLElement* parentEle=element;
        while(true)
        {
            int idx=name.find_first_of('.');
            if(idx==std::string::npos)
            {
                XMLElement* ele=doc.NewElement(name.c_str());
                ele->SetAttribute("value",it.second.c_str());
                parentEle->InsertEndChild(ele);
                break;
            }
            std::string parentName=name.substr(0,idx);
            name=name.substr(idx+1);
            XMLElement* ele=parentEle->FirstChildElement(parentName.c_str());
            if(!ele)
            {
                ele=doc.NewElement(parentName.c_str());
                parentEle->InsertEndChild(ele);
            }
            parentEle=ele;
        }
    }

    if(XML_SUCCESS!=doc.SaveFile(filename)) {doc.PrintError();return false;}
    return true;
}

inline bool exportEle1(GSLAM::Svar& var, XMLElement* ele, std::string parentName="")
{
    if(!ele) return false;
    if(ele->Attribute("value"))
        var.insert((parentName.empty()?std::string():parentName+".")+ele->Name(),ele->Attribute("value"));
    XMLElement* child=ele->FirstChildElement();
    while(child)
    {
        exportEle1(var,child,(parentName.empty()?std::string():parentName+".")+ele->Name());
        child=child->NextSiblingElement();
    }
    return true;
}

inline bool loadSvarXML1(GSLAM::Svar& var, std::string filepath)
{
    XMLDocument doc;
    if(XML_SUCCESS!=doc.LoadFile(filepath.c_str())) return false;
    XMLElement* element=doc.FirstChildElement("project");
    element->SetName("");
    return exportEle1(var,element);
}

} // end of namespace tinyxml2

#endif // end of __XML_UTILS_H__


